<?php
/**
 * Created by PhpStorm.
 * User: dell
 * Date: 2019/9/27
 * Time: 9:24
 */

namespace app\controller\api;


use app\BaseController;
use app\models\goods\GoodsModel;
use app\models\order\OrderDetailModel;
use app\models\order\OrderModel;
use app\models\order\OrderRecordModel;
use app\models\order\RechargeOrderModel;
use app\models\user\UserModel;
use app\services\config\ConfigService;
use app\services\order\OrderService;
use app\services\user\DetailMoneyService;
use app\services\utils\LockService;
use think\facade\Db;
use think\Request;
use wxpay\WxpayNotify;

class NotifyController extends BaseController
{

    protected $middleware = [
//        'AliNotify' => ['only' => ['aliPayNotify']],
//        'WxNotify' => ['only' => ['wxPayNotify', 'wxRechargeNotify']]
    ];

    /**
     * 支付宝订单支付回调
     * @param Request $request
     * @return string
     */
    public function aliPayNotify(Request $request)
    {

        //file_put_contents('aliPayNotify.txt',date('m-d H:i:s')."支付宝支付回调\n",FILE_APPEND);

        require '../extend/AlipaySDK/aop/AopClient.php';
        require_once '../extend/AlipaySDK/aop/request/AlipayTradeAppPayRequest.php';

        // 获取支付宝 POST 过来反馈信息
        $alipayNotify = $_POST;

        //file_put_contents('alipay_notify2.txt',date('m-d H:i:s').json_encode($alipayNotify)."\n",FILE_APPEND);

        if(empty($alipayNotify)){
            // 验签失败
            echo 'failed';
            die;
        }

        // 验证签名
        // 例如 require_once('alipay-sdk-PHP/AopSdk.php');
        $aop = new \AopClient();
        $aop->alipayrsaPublicKey = 'MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEArxCK1KnV4MnXOKsDkKfMwUB1s0maYZW7SFhbbF0ob2Y947YA8m8nwZ5wI9Ulfwfb1hhAUWulqOEoL5qZztK+TTyh5HlAmkl5xzdxkGrdCE1WTGiY+m4k5vJQTKVACbDinc3vchbXbVps+76d2yv+OMfJVska3CKjywSGH4sqLRnR9cZk09FoFVctJvCB85Tm+3WuHTOPXwE1/M+94d2vEDWdWC3/aEFS/xO0kt7GQNkr4uGqtN3u/B4CBhaJLYck4iPbzRSCgagTnuaiw5wiiuaoJ/UHu486Iobql3lhclsEWibhMZ2qMJuT3q3vC7sCc/pmu29bsFCT4bbHgwm4JwIDAQAB';
        $rsaPublicKeyFilePath = 'file://'.public_path().'merchant_cert/alipayPublicKey_RSA2.txt';
        $signVerified = $aop->rsaCheckV1($alipayNotify, $rsaPublicKeyFilePath, "RSA2");

        // 如果签名验证通过
        if ($signVerified) {

            //判断是否已经处理过订单
            $record = OrderRecordModel::where('order_sn',$alipayNotify['out_trade_no'])->where('pay_status',2)->find();
            if($record){
                echo 'success';
                die;
            }

//  $alipayNotify 数据结构
//            {
//                "notify_time": "2024-05-20 14:30:45", 通知时间
//                "notify_type": "trade_status_sync", 通证类型
//                "notify_id": "70fec1c2730b275d2e7a7b009c6935ceeY", 通知校验 ID
//                "app_id": "your_app_id", 开发者的 app_id
//                "charset": "utf-8",
//                "version": "1.0",
//                "sign_type": "RSA2",
//                "sign": "xxxxxx", // 签名字符串
//                "trade_no": "2024052021001004100503015581", 支付宝交易号
//                "out_trade_no": "20240520X63284", 商户订单号
//                "buyer_id": "2088102114478787", 买家支付宝用户 ID
//                "seller_id": "2088102115416991", 卖家支付宝用户 ID
//                "trade_status": "TRADE_SUCCESS", 交易状态，具体状态参考支付宝文档
//                "total_amount": "100.00", 订单金额
//                "receipt_amount": "98.00", 实收金额
//                "buyer_pay_amount": "100.00", 付款金额
//                "gmt_create": "2024-05-20 14:30:31", 交易创建时间
//                "gmt_payment": "2024-05-20 14:30:45", 交易付款时间
            //"gmt_refund":"" //交易退款时间
            //"gmt_close":"", //交易结束时间
//                "fund_bill_list": [{ //支付金额信息
//                            "amount": "100.00",
//                    "fund_channel": "ALIPAYACCOUNT"
//                }],
//                "passback_params": "your_custom_params" //回传参数，可以是商户自定义参数
//            }



            // 处理你的逻辑，例如更新订单状态等
            $orderList = OrderModel::where('union_order_sn',$alipayNotify['out_trade_no'])->select();

            foreach($orderList as $key => $orderInfo){
                $this->notify($orderInfo['order_sn']);
                $user_id = $orderInfo['user_id'];
            }

            if($orderList){
                //记录第三方支付信息
                OrderRecordModel::create([
                    'user_id' => $user_id,
                    'order_id' => $orderInfo['id'],
                    'order_type' => $orderInfo['order_type'],
                    'order_sn' => $alipayNotify['out_trade_no'],
                    'total_amount' => $alipayNotify['total_amount'],
                    'pay_amount' => $orderInfo['pay_amount'],
                    'pay_time' => strtotime($alipayNotify['gmt_payment']),
                    'pay_status' => 1,
                    'create_time' => time(),
                    'update_time' => time(),
                    'trade_no' => $alipayNotify['trade_no'],
                    'pay_notify' => json_encode($alipayNotify),
                    'receipt_amount' => $alipayNotify['receipt_amount'],
                    'buyer_pay_amount' => $alipayNotify['buyer_pay_amount'],
                ]);
            }
            file_put_contents('aliPayNotify.txt',date('m-d H:i:s')."支付完成\n",FILE_APPEND);

            // 返回成功响应给支付宝
            echo 'success';
        } else {
            // 验签失败
            echo 'failed';
        }
        die;
    }

    /**
     * 微信订单支付回调
     * @param Request $request
     * @return string
     */
    public function wxPayNotify(Request $request)
    {
        return $this->notify($request->order_id, 2);
        $apikey = ConfigService::getConfigValue('wechat_app_secret');
        $wxPay = new WxpayNotify($apikey);
        $result = $wxPay->validate();
        if($result===false){
            //验证签名失败
            exit('sign error');
        }
        $result = $wxPay->notify();
        if ($result === false) {
            exit('pay error');
        }
        if ($result['trade_state'] == 'SUCCESS') {
            OrderService::handleOrder($result['out_trade_no']);
            //支付成功，完成你的逻辑
            //例如连接数据库，获取付款金额$result['amount']['total']，获取订单号$result['out_trade_no']修改数据库中的订单状态等;
            //订单总金额，单位为分：$result['amount']['total']
            //用户支付金额，单位为分：$result['amount']['payer_total']
            //商户订单号：$result['out_trade_no']
            //微信支付订单号：$result['transaction_id']
            //银行类型：$result['bank_type']
            //支付完成时间：$result['success_time'] 格式为YYYY-MM-DDTHH:mm:ss+TIMEZONE
            //用户标识：$result['payer']['openid']
            //交易状态：$result['trade_state']
            //具体详细请看微信文档：https://pay.weixin.qq.com/wiki/doc/apiv3/wxpay/pay/transactions/chapter3_11.shtml
            echo 'success';
        }


    }

    /**
     * 订单处理
     * @param $orderSn
     * @param $transId
     * @return string
     */
    public function notify($orderSn, $transId = '')
    {
        OrderService::handleOrder($orderSn);
    }

    /**
     * 微信余额充值回调
     * @param Request $request
     * @return string
     */
    public function wxRechargeNotify(Request $request)
    {
        $request->order_id = $this->request->param('order_id');
        $request->transaction_id = $this->request->param('transaction_id');
        return $this->rechargeNotify($request->order_id, $request->transaction_id);
    }

    /**
     * 支付宝余额充值回调
     * @param Request $request
     * @return string
     */
    public function aliPayRechargeNotify(Request $request)
    {
        require '../extend/AlipaySDK/aop/AopClient.php';
        require_once '../extend/AlipaySDK/aop/request/AlipayTradeAppPayRequest.php';
        // 获取支付宝 POST 过来反馈信息
        $alipayNotify = $_POST;

        file_put_contents('aliPayRechargeNotify.txt',date('m-d H:i:s').json_encode($alipayNotify)."\n",FILE_APPEND);

        if(empty($alipayNotify)){
            // 验签失败
            echo 'failed';
            die;
        }

        // 验证签名
        // 例如 require_once('alipay-sdk-PHP/AopSdk.php');
        $aop = new \AopClient();
        $aop->alipayrsaPublicKey = 'MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEArxCK1KnV4MnXOKsDkKfMwUB1s0maYZW7SFhbbF0ob2Y947YA8m8nwZ5wI9Ulfwfb1hhAUWulqOEoL5qZztK+TTyh5HlAmkl5xzdxkGrdCE1WTGiY+m4k5vJQTKVACbDinc3vchbXbVps+76d2yv+OMfJVska3CKjywSGH4sqLRnR9cZk09FoFVctJvCB85Tm+3WuHTOPXwE1/M+94d2vEDWdWC3/aEFS/xO0kt7GQNkr4uGqtN3u/B4CBhaJLYck4iPbzRSCgagTnuaiw5wiiuaoJ/UHu486Iobql3lhclsEWibhMZ2qMJuT3q3vC7sCc/pmu29bsFCT4bbHgwm4JwIDAQAB';
        $rsaPublicKeyFilePath = 'file://'.public_path().'merchant_cert/alipayPublicKey_RSA2.txt';
        $signVerified = $aop->rsaCheckV1($alipayNotify, $rsaPublicKeyFilePath, "RSA2");

        // 如果签名验证通过
        if ($signVerified) {
            return $this->rechargeNotify($alipayNotify['out_trade_no'], $alipayNotify['trade_no']);
        } else {
            // 验签失败
            echo 'failed';
        }
        die;
    }

    /**
     * 余额充值方法
     * @param $orderSn
     * @param $transId
     * @return string
     */
    public function rechargeNotify($orderSn, $transId)
    {

        try {
            $order = Db::name('recharge_order')->where('order_sn',$orderSn)->find();
            if(!$order){
                return 'error';
            }
            if($order['is_pay']){
                return 'error';
            }
            Db::name('recharge_order')->where('order_sn',$orderSn)->update([
                'is_pay' => 1,
                'pay_time' => time(),
                'transaction_id' => $transId,
            ]);
            $type = DetailMoneyService::RECHARGE;
            DetailMoneyService::create($order['user_id'],$type,$order['amount'],$orderSn);
            return 'success';
        } catch (\Exception $exception) {
            return 'error';
        }
    }
}
